"""
试卷B第二题答案！！！
题目 2：进程间通信 - 分布式文件处理（30 分）
模拟分布式系统中的文件处理流程，要求：
创建一个任务分发进程：
读取input_files.txt（包含 100 个文件名），将文件名分发给工作进程。
创建 4 个工作进程：
从任务队列获取文件名，读取对应文件内容（文件内容为随机整数，每行一个）。
计算文件中所有整数的平方和，将结果写入新文件（例如：output_原文件名）。
创建一个结果收集进程：
读取所有输出文件，统计平方和的总和，写入final_result.txt。
使用multiprocessing.Manager创建共享队列，确保进程间通信安全。
主程序等待所有任务完成后，验证final_result.txt的正确性。

评分标准:
队列与进程创建	8 分	正确创建任务分发、工作进程和结果收集进程，使用共享队列
任务分发与文件读取	6 分	正确读取输入文件，分发给工作进程，无任务丢失
计算与结果写入	10 分	工作进程正确计算平方和，结果收集进程汇总结果并写入最终文件
进程协调与验证	4 分	所有进程正常结束，验证最终结果文件的正确性
代码健壮性	2 分	处理文件不存在或格式错误的情况



"""
import multiprocessing
import random
def create_input_files():
    with open("input_files.txt", "w") as f:
        for i in range(1, 101):
            filename = f"file{i}.txt"
            f.write(f"{filename}\n")
            with open(filename, "w") as data_file:
                data_file.write("\n".join(str(random.randint(1, 100)) for _ in range(1000)))

def task_distributor(task_queue):
    with open("input_files.txt", "r") as f:
        for line in f:
            task_queue.put(line.strip())
    for _ in range(4):  # 发送结束信号给4个工作进程
        task_queue.put(None)

def worker(task_queue, result_queue, worker_id):
    while True:
        filename = task_queue.get()
        if filename is None:
            break
        try:
            with open(filename, "r") as f:
                numbers = [int(line.strip()) for line in f]
            square_sum = sum(num ** 2 for num in numbers)
            output_filename = f"output_{filename}"
            with open(output_filename, "w") as f:
                f.write(str(square_sum))
            result_queue.put(output_filename)
        except Exception as e:
            print(f"Worker {worker_id} 处理 {filename} 出错: {e}")


def result_collector(result_queue, total_tasks):
    grand_total = 0
    for _ in range(total_tasks):
        output_file = result_queue.get()
        with open(output_file, "r") as f:
            grand_total += int(f.read().strip())
    with open("final_result.txt", "w") as f:
        f.write(str(grand_total))
    return grand_total


if __name__ == "__main__":
    create_input_files()

    with multiprocessing.Manager() as manager:
        task_queue = manager.Queue()
        result_queue = manager.Queue()

        distributor = multiprocessing.Process(target=task_distributor, args=(task_queue,))
        workers = [multiprocessing.Process(target=worker, args=(task_queue, result_queue, i)) for i in range(1, 5)]
        collector = multiprocessing.Process(target=result_collector, args=(result_queue, 100))

        distributor.start()
        for w in workers:
            w.start()
        collector.start()

        distributor.join()
        for w in workers:
            w.join()
        collector.join()

        # 验证结果
        with open("final_result.txt", "r") as f:
            final_result = int(f.read())

        # 计算预期结果
        expected_total = 0
        for i in range(1, 101):
            with open(f"file{i}.txt", "r") as f:
                numbers = [int(line.strip()) for line in f]
            expected_total += sum(num ** 2 for num in numbers)

        print(f"最终结果: {final_result}")
        print(f"预期结果: {expected_total}")
        print(f"验证结果: {'正确' if final_result == expected_total else '错误'}")